/*
 * FastaRecord.java
 *
 * Created on September 26, 2006, 1:03 PM
 * Brought forward from bugs2
 */

package biofilter.records;

import biofilter.exceptions.InvalidRecordException;
import java.util.logging.Level;
import java.util.logging.Logger;

/**
 *  Container for a fasta file and a quality file
 *
 */
public class FastaRecord implements Record {
    private String header;
    private String content;
    private String qualityContent;
    private String fastaString;

    public FastaRecord() {
    }
    
    public FastaRecord(String r) throws InvalidRecordException {
        this.fastaString = r;
        parse(r);
    }
    
    
    /** Calls parse to establish valid FASTA record. */
    public void set(String r) throws IllegalArgumentException {
        try {
            parse(r);
        } catch (IllegalArgumentException ex) {
            Logger.getLogger(FastaRecord.class.getName()).log(Level.SEVERE, null, ex);
            throw new IllegalArgumentException("could not parse " + r, ex);
        }
    }
    
    
    /** Gets a Fasta record in proper format (header plus content). */
    public String get() 
    {
        return this.fastaString;
        //return ">"+header+"\n"+content+"\n";
    }
    
    /** Gets quality values in proper format (header plus content). */
    public String getQuality() 
    {
        return ">"+header+"\n"+qualityContent+"\n";
    }
  
    /** Gets the header part of a FASTA record. */
    public String getHeader() 
    {
	return this.header;
    }
    
    /** Gets the content section of a FASTA record.

     */
    public String getContent() 
    {
        return this.content;
    } 
    
    /** Gets the content section of the quality.
     * The quality content is a string of white space seperated base quality
     * scores. The quality scores themselves, while in string representation,
     * are positive integers. It is generally assumed that these quality scores
     * are those like phred scores, ie a score of 10 is one error in 10, a 
     * score of 20 is one error in 100, a score of 30 is one error in 1000 and
     * so on. Phred does not produce a score less than 1 or greater than 99, but
     * don't always assume that the scores were calculated by phred.
     * @return String the quality representation of the string.
     */
    public String getQualityContent() 
    {
        return this.qualityContent;
    } 

    
    /** Internal parsing method to identify the header and content sections
     * of a FASTA record */
    private void parse(String r) throws IllegalArgumentException {
        if(!r.startsWith(">")) {
            throw new IllegalArgumentException("Not header, header must start wtih >");
        }

        int endHeader=r.indexOf("\n");

        if(endHeader==-1) {
            throw new IllegalArgumentException("Sequence content not found in " + r);
        }

        header = r.substring(1,endHeader);
        String r_sub = r.substring(endHeader+1);
        
        int qHeader = r_sub.indexOf(">");
        if(qHeader == -1){//no quality values
            // hard returns would be included in content if they existed.
            content = r_sub;
        } else {
            if(qHeader == 0) {
                throw new IllegalArgumentException(
                        "Sequence not found before header for quality values in " + r);
            }
            content = r_sub.substring(0, qHeader-1);
            String r_sub_sub = r_sub.substring(qHeader);
            int endQHeader = r_sub_sub.indexOf("\n");
            this.qualityContent = r_sub_sub.substring(endQHeader+1);
        }
    }
}